/******************************/
/* 描述：解析策划表工具生成的文件 */
/* 作者：by 杉木说 */
/* 日期：2022-12-02 */
/* 修改：2023-04-06 */
/******************************/

const Utils = require('./Utils');
const fs = require('fs');
const zlib = require('zlib');
const path = require('path');


/** 需要被读取的配置文件的地址 */
let readFilePath, outputDir;
/** split/lcdat文件的解密密钥 */
let decryptCode;

/** 遍历目录 */
function traverseDirectorySync(targetDirectoryPath) {

    const files = fs.readdirSync(targetDirectoryPath);

    files.forEach(file => {
        const filePath = path.join(targetDirectoryPath, file);

        if (fs.statSync(filePath).isDirectory()) {
            traverseDirectorySync(filePath); // 递归遍历子目录
        } else {
            if (file.endsWith(".split.bytes") || file.endsWith(".lcdat.bytes")) {
                handleReadStream(filePath, file.endsWith(".split.bytes"));
            }
        }
    });
}

/** 读取数据方法 */
function handleReadStream(fileReadPath, split = false) {
    // 创建读取流
    const readStream = fs.createReadStream(fileReadPath);
    // 创建解压缩器
    const gunzip = zlib.createGunzip();
    // 读取流通过解压缩器进行解压缩
    readStream.pipe(gunzip);
    // 用一个缓冲区来存储解压缩后的数据
    let buffer = Buffer.from('');
    gunzip.on('data', (data) => { buffer = Buffer.concat([buffer, data]); });
    gunzip.on('end', () => {
        let jsonStr = "";
        try {
            jsonStr = JSON.parse(Utils.XORDecrypt(buffer.toString(), decryptCode))
        } catch (error) {
            console.log("!!! 错误: 读取后Json解析失败!请检查加密解密的密钥是否一致!");
            console.log("!!! 错误: 文件地址!", fileReadPath);
            return;
        }
        split ? outputSplit(jsonStr, fileReadPath) : output(fileReadPath, jsonStr);
    });
}

/**
 * 获取工具的配置文件
 */
function getToolConfig() {
    let cfgJson = Utils.getToolConfigs();

    decryptCode = cfgJson.ReadConfig.DecryptCode;
    readFilePath = cfgJson.ReadConfig.ReadFilePath;
    outputDir = path.join(readFilePath, "Output-Josn");
}

/**
 * 输出为json文件(总的)
 */
function output(fileReadPath, data) {
    // 每个配置表单独生成 json文件
    let total = Object.keys(data).length;;
    let index = 0;
    console.log("\nStart .lcdat => ", fileReadPath);
    for (const key in data) {
        if (Object.hasOwnProperty.call(data, key)) {
            const cfg = data[key];
            let singleJsonStr = JSON.stringify(cfg);
            // console.log(singleJsonStr);
            // 每个配置表单独输出
            let __path = path.join(outputDir, key + ".json");
            // 处理未存在的文件夹
            Utils.checkAndMkDir(outputDir);
            fs.writeFileSync(__path, singleJsonStr);
            index++;
            console.log(`Successful .lcdat: ${key} analysis successful!!! (${index}/${total})`);
        }
    }

    console.log("温馨提示: 配置文件(.lcdat)解析完成! " + fileReadPath.toUpperCase(), "\n");
}

/**
 * 输出为json文件(split)
 */
function outputSplit(data, fileReadPath) {
    let baseName = path.basename(fileReadPath, path.extname(fileReadPath));
    let singleJsonStr = JSON.stringify(data);

    // 每个配置表单独输出
    let __path = path.join(outputDir, "Split", baseName + ".json");

    // 处理未存在的文件夹
    Utils.checkAndMkDir(path.dirname(__path));
    fs.writeFileSync(__path, singleJsonStr);

    console.log(`Analysis: Successful .split: ${baseName} analysis successful!!! =>> ${fileReadPath}`);
}

// start
getToolConfig();
traverseDirectorySync(readFilePath);